package streaming

import (
	"context"
	"time"
)

// StreamState represents the state of a stream
type StreamState int

const (
	StreamStateInitialized StreamState = iota
	StreamStateRunning
	StreamStatePaused
	StreamStateStopped
	StreamStateError
)

// String returns the string representation of the stream state
func (s StreamState) String() string {
	switch s {
	case StreamStateInitialized:
		return "INITIALIZED"
	case StreamStateRunning:
		return "RUNNING"
	case StreamStatePaused:
		return "PAUSED"
	case StreamStateStopped:
		return "STOPPED"
	case StreamStateError:
		return "ERROR"
	default:
		return "UNKNOWN"
	}
}

// StreamMetrics tracks stream performance metrics
type StreamMetrics struct {
	StartTime       time.Time
	LastEventTime   time.Time
	Duration        time.Duration
	EventsSent      int64
	EventsProcessed int64
	BytesSent       int64
	BytesProcessed  int64
	Errors          int64
}

// StreamEvent represents a streaming response event
type StreamEvent struct {
	Type    string // Type of event (e.g., "token", "complete", "error")
	Content string // Content of the event (token or error message)
	Token   string // Deprecated: use Content instead
	Done    bool   // Whether this is the last event
	Error   error  // Error if any occurred
}

// StreamConfig contains configuration for streaming
type StreamConfig struct {
	MaxTokens   int
	Temperature float32
	TopP        float32
	Stop        []string
	Model       string
}

// NewDefaultStreamConfig creates a default stream configuration
func NewDefaultStreamConfig() *StreamConfig {
	return &StreamConfig{
		MaxTokens:   2000,
		Temperature: 0.7,
		TopP:        1.0,
		Stop:        []string{},
		Model:       "gpt-3.5-turbo",
	}
}

// StreamResponse represents a streaming response
type StreamResponse struct {
	Content string
	Done    bool
}

// StreamOptions represents options for streaming
type StreamOptions struct {
	MaxTokens   int
	Temperature float64
	TopP        float64
	Stop        []string
	Model       string
}

// StreamHandler defines the interface for handling streaming responses
type StreamHandler interface {
	// OnEvent is called for each event in the stream
	OnEvent(event *StreamEvent) error

	// OnComplete is called when the stream is complete
	OnComplete(ctx context.Context) error

	// OnError is called when an error occurs
	OnError(ctx context.Context, err error) error

	// GetText returns the accumulated text from the stream
	GetText() string
}

// DefaultStreamHandler provides a default implementation of StreamHandler
type DefaultStreamHandler struct {
	OnEventFunc    func(event *StreamEvent) error
	OnCompleteFunc func(ctx context.Context) error
	OnErrorFunc    func(ctx context.Context, err error) error
	text           string // accumulated text
}

// OnEvent implements StreamHandler
func (h *DefaultStreamHandler) OnEvent(event *StreamEvent) error {
	if event != nil {
		h.text += event.Content
	}
	if h.OnEventFunc != nil {
		return h.OnEventFunc(event)
	}
	return nil
}

// OnComplete implements StreamHandler
func (h *DefaultStreamHandler) OnComplete(ctx context.Context) error {
	if h.OnCompleteFunc != nil {
		return h.OnCompleteFunc(ctx)
	}
	return nil
}

// OnError implements StreamHandler
func (h *DefaultStreamHandler) OnError(ctx context.Context, err error) error {
	if h.OnErrorFunc != nil {
		return h.OnErrorFunc(ctx, err)
	}
	return err
}

// GetText returns the accumulated text from the stream
func (h *DefaultStreamHandler) GetText() string {
	return h.text
}
